//queue1.cpp
/********************************************************************************
*																				*
*	Author:			Jared Szechy												*
*	Assignment:		Assignment 6												*
*	Class:			CPS-151														*
*	Instructor:		V. Starkley													*
*	Due Date:		October 13													*
*																				*
*	This file implements the queue class.										*
*																				*
********************************************************************************/

template<class ItemType>
QueType<ItemType>::QueType()		
{
    maxQue = MAX_ITEMS + 1;  //need to add a "reserved space"
    front = maxQue - 1;
    rear = maxQue - 1;
    items = new ItemType[maxQue];
	if (items == NULL)
	{
		cout << "Error creating queue.\n";
		exit(1);
	}
}

template<class ItemType>
QueType<ItemType>::QueType(int max)
{
    maxQue = max + 1;  //need to add a "reserved space"
    front = maxQue - 1;
    rear = maxQue - 1;
    items = new ItemType[maxQue];
	if (items == NULL)
	{
		cout << "Error creating queue.\n";
		exit(1);
	}
}


template<class ItemType>
QueType<ItemType>::QueType(const QueType& source)
{
	//copy non-dynamic private variables
	maxQue = source.maxQue;
	front = source.front;
	rear = source.rear;

	//allocate new items array
	items = new ItemType[maxQue];
	if (items == NULL)
	{
		cout << "Error creating queue.\n";
		exit(1);
	}

	//copy elements from source array to self array
	int i = source.front;
	while (i != source.rear)
	{
		i = (i+1)% maxQue;
		items[i] = source.items[i];
	}
}


template<class ItemType>
QueType<ItemType>::~QueType()
{
	delete[] items;
}


template<class ItemType>
QueType<ItemType> QueType<ItemType>::operator = (const QueType<ItemType>& source)
{
	//check x == x case
	if (this == &source)
		return *this;

	//delete existing array
	delete[] items;

	//re-create array and copy source to self
	//copy non-dynamic private variables
	maxQue = source.maxQue;
	front = source.front;
	rear = source.rear;

	//allocate new items array
	items = new ItemType[maxQue];
	if (items == NULL)
	{
		cout << "Error creating queue.\n";
		exit(1);
	}

	//copy elements from source array to self array
	int i = source.front;
	while (i != source.rear)
	{
		i = (i+1)% maxQue;
		items[i] = source.items[i];
	}

	return *this;
}

template<class ItemType>
void QueType<ItemType>::MakeEmpty()
{
    front = maxQue - 1;
    rear = maxQue - 1;
}

template<class ItemType>
bool QueType<ItemType>::IsEmpty() const
{
    return (rear == front);
}

template<class ItemType>
bool QueType<ItemType>::IsFull() const
{
    return ((rear + 1) % maxQue == front);
}

template<class ItemType>
bool QueType<ItemType>::Enqueue(ItemType newItem)
{
	if ((rear+1) % maxQue == front)
		return false;
    rear = (rear +1) % maxQue;
    items[rear] = newItem;
	return true;
}

template<class ItemType>
bool QueType<ItemType>::Dequeue(ItemType& item)
{
	if (rear == front)
		return false;
    front = (front + 1) % maxQue;
    item = items[front];
	return true;
}